/**
 * 
 */
package sap.provider;

import com.sap.mw.jco.JCO;

import data.MessageType;
import data.ReturnValue;
import exceptions.DetailedReturnException;
import exceptions.ReturnException;

/**
 * @author sebastian
 *
 */
public final class Return {
	/**
	 * Call this function to generate a new {@link ReturnValue} from a
	 *  {@link JCO.Structure}
	 * 
	 * @param struct the {@link JCO.Structure} which has to be an "SAP RETURN
	 *  structure" (or something similar)
	 * @return the newly generated {@link ReturnValue}
	 * @throws JCO.ConversionException thrown if a value could not be converted
	 * @throws JCO.Exception thrown if a field does not exist
	 */
	public static ReturnValue getFromStructure(JCO.Record struct)
			throws JCO.ConversionException, JCO.Exception {
		ReturnValue result = new data.ReturnValue();
		try {
			result.type = charToType(struct.getChar("TYPE"));
		} catch (JCO.Exception ex) {
			result.type = charToType(struct.getChar("MESSAGE_TYPE"));
		}
		try {
			result.message = struct.getString("MESSAGE");
		} catch (JCO.Exception ex) {
			result.message = struct.getString("MESSAGE_TEXT");
		}
		try {
			result.id = struct.getString("ID");
		} catch (JCO.Exception ex) {
			result.id = struct.getString("MESSAGE_ID");
		}
		try {
			result.number = struct.getInt("NUMBER");
		} catch (JCO.Exception ex) {
			result.number = struct.getInt("MESSAGE_NUMBER");
		}
		
		return result;
	}
	
	public static ReturnValue[] getFromTable(JCO.Table table) {
		int num = table.getNumRows();
		ReturnValue[] result = new  ReturnValue[num];
		for (int i=0; i<num; i++) {
			result[i] = getFromStructure(table);
			table.nextRow();
		}
		
		return result;
	}
	
	public static void testReturnValue(ReturnValue r)
			throws ReturnException {
		if (!checkSuccess(r.type))
			throw new ReturnException(r);
	}
	
	public static void testReturnValue(ReturnValue r, ReturnValue[] detail) {
		// TODO find exceptions
		
		if (r == null) {
			for (int i=0; i<detail.length; i++) {
				if (!checkSuccess(detail[i].type)) {
					r = detail[i];
					break;
				}
			}
		}
		
		if (r != null && !checkSuccess(r.type))
			throw new DetailedReturnException(r, detail);
	}
	
	private static MessageType charToType(char type)
			throws EnumConstantNotPresentException {
		switch (type) {
		case ' ':
		case 'S':
			return MessageType.SUCCESS;
		case 'I':
			return MessageType.INFORMATION;
		case 'W':
			return MessageType.WARNING;
		case 'E':
			return MessageType.ERROR;
		default:
			throw new EnumConstantNotPresentException(MessageType.class, type+"");
		}
	}
	
	private static boolean checkSuccess(MessageType t) {
		return t == MessageType.SUCCESS/* || t == MessageType.INFORMATION*/;
	}
}
